<template>
  <div ref="container" class="three-d-container" />
</template>

<script lang="ts">
import { defineComponent, onMounted, ref } from 'vue';
import * as THREE from 'three';
import { OrbitControls } from 'three/addons/controls/OrbitControls.js';
import { GLTFLoader } from 'three/addons/loaders/GLTFLoader.js';
import { RGBELoader } from 'three/addons/loaders/RGBELoader.js';

type GLTF = {
  scene: THREE.Group;
};

export default defineComponent({
  name: 'ThreeDModel',
  setup() {
    const container = ref<HTMLDivElement | null>(null);

    const init3D = async () => {
      if (!container.value) return;

      const scene = new THREE.Scene();
      const camera = new THREE.PerspectiveCamera(75, window.innerWidth / window.innerHeight, 0.1, 1000);
      const renderer = new THREE.WebGLRenderer({
        antialias: true,
        powerPreference: "high-performance"
      });

      // 新版Three.js颜色空间设置
      renderer.outputColorSpace = THREE.SRGBColorSpace;
      renderer.toneMapping = THREE.ACESFilmicToneMapping;
      renderer.toneMappingExposure = 0.8;

      renderer.setSize(window.innerWidth, window.innerHeight);
      container.value.appendChild(renderer.domElement);

      // 加载HDR环境贴图
      try {
        const hdrLoader = new RGBELoader();
        const hdrTexture = await hdrLoader.loadAsync(
            '/src/assets/img/4k.hdr' // 请确认实际路径
        );
        hdrTexture.mapping = THREE.EquirectangularReflectionMapping;
        scene.environment = hdrTexture;
        scene.background = hdrTexture;
      } catch (error) {
        console.error('HDR加载失败:', error);
      }

      // 加载3D模型
      const loader = new GLTFLoader();
      loader.load(
          '/src/assets/model/图书馆.glb',
          (gltf: GLTF) => {
            gltf.scene.traverse((child: THREE.Object3D) => {
              if (child instanceof THREE.Mesh) {
                const material = child.material as THREE.MeshStandardMaterial;

                // 确保材质属性存在
                if (material) {
                  material.envMapIntensity = 1.5;
                  material.needsUpdate = true;

                  // 兼容新版物理材质设置
                  if (material.isMeshStandardMaterial) {
                    material.metalness = 0.2;
                    material.roughness = 0.5;
                  }
                }
              }
            });

            scene.add(gltf.scene);
            gltf.scene.scale.set(0.5, 0.5, 0.5);
            gltf.scene.position.set(0, -1, 0);
          },
          undefined,
      );

      // 光源调整
      const ambientLight = new THREE.AmbientLight(0x404040, 0.8);
      scene.add(ambientLight);

      const directionalLight = new THREE.DirectionalLight(0xffffff, 1.2);
      directionalLight.position.set(5, 5, 5).normalize();
      scene.add(directionalLight);

      camera.position.set(2, 2, 5);

      // 控制器设置
      const controls = new OrbitControls(camera, renderer.domElement);
      controls.enableDamping = true;
      controls.dampingFactor = 0.05;
      controls.minDistance = 2;
      controls.maxDistance = 15;

      // 响应式调整
      window.addEventListener('resize', () => {
        camera.aspect = window.innerWidth / window.innerHeight;
        camera.updateProjectionMatrix();
        renderer.setSize(window.innerWidth, window.innerHeight);
      });

      // 动画循环
      const animate = () => {
        requestAnimationFrame(animate);
        controls.update();
        renderer.render(scene, camera);
      };

      animate();
    };

    onMounted(() => {
      init3D();
    });

    return { container };
  }
});
</script>

<style scoped>
.three-d-container {
  width: 100%;
  height: 100vh;
  overflow: hidden;
}
</style>
